package com.youshang520i.condition;

import com.support.annotation.ConditionOnClass;
import org.springframework.beans.factory.support.AbstractBeanDefinition;
import org.springframework.beans.factory.support.BeanDefinitionBuilder;
import org.springframework.beans.factory.support.GenericBeanDefinition;
import org.springframework.context.annotation.Condition;
import org.springframework.context.annotation.ConditionContext;
import org.springframework.core.type.AnnotatedTypeMetadata;

import java.util.Map;

/**
 * condition会在所有方法之前之前执行
 * 在BeanFactory初始化的时候进行添加判断是否需要对实现Condition的类进行初始化
 *
 * @author youshang
 */
public class MyCondition implements Condition {
    @Override
    public boolean matches(ConditionContext conditionContext, AnnotatedTypeMetadata annotatedTypeMetadata) {
        Map<String, Object> annotationAttributes = annotatedTypeMetadata.getAnnotationAttributes(ConditionOnClass.class.getName());
        if (null != annotationAttributes) {
            Object o = annotationAttributes.get("clazz");
            String canonicalName = ((Class) o).getCanonicalName();
            String str = "com.youshang520i.model.Student";
            if (str.equals(canonicalName)) {
                AbstractBeanDefinition rawBeanDefinition = null;
                try {
                    BeanDefinitionBuilder beanDefinitionBuilder = BeanDefinitionBuilder.genericBeanDefinition(Class.forName(canonicalName));
                    rawBeanDefinition = beanDefinitionBuilder.getRawBeanDefinition();
                    rawBeanDefinition.setAutowireMode(GenericBeanDefinition.AUTOWIRE_BY_NAME);
                } catch (ClassNotFoundException e) {
                    e.printStackTrace();
                }
                //此处注册的Bean会在ClassPathBeanDefinitionScanner.doScan()方法中统一注册
                //registerBeanDefinition(definitionHolder, this.registry);
                //存在this.registry.beanDefinitionMap中
                conditionContext.getRegistry().registerBeanDefinition("student", rawBeanDefinition);
                return true;
            }
        }
        return false;
    }
}
